﻿// ***********************************************************************
// Assembly         : MVC4Portal
// Author           : LJO+01 (Laurent Jordi)
// Created          : 06-05-2013
// Last Modified By : LJO+01 (Laurent Jordi)
// Last Modified On : 06-05-2013
// ***********************************************************************
// <copyright file="FirendlyURLAnalyzer.cs" company="Copyright © Innovacall 2011">
//     Copyright (c) Copyright © Innovacall 2011. All rights reserved.
// </copyright>
// <summary></summary>
// ***********************************************************************
using System;
using System.Collections.Generic;
using System.Configuration;
using System.Globalization;
using System.Linq;
using System.Threading;
using System.Web;
using System.Web.Security;
using InnovaApp.Layers.DataLayer;
using InnovaApp.Layers.DomainLayer;
using InnovaApp.Layers.ResourcesLayer.Properties;
using InnovaApp.Portals.MVC4Portal.Models.MetaModels;
using INNOVACALL.Framework.Common;
using INNOVACALL.Framework.Common.InnovacallExceptions;
using INNOVACALL.Framework.Common.Logging;

namespace InnovaApp.Portals.MVC4Portal.Controllers.FriendlyURLHandling
{
    /// <summary>
    /// Classe d'extension de string dédiée à l'annalyse d'une chaine FriendlyURL
    /// </summary>
    public static class FirendlyURLAnalyzer
    {
        /// <summary>
        /// The e method base
        /// </summary>
        private static string eMethodBase = "InnovaApp.Portals.MVC4Portal.Controllers.FriendlyURLHandling.FirendlyURLAnalyzer";
        /// <summary>
        /// Méthode d'extension récupérant les données de routage
        /// </summary>
        /// <param name="friendlyUrl">The friendly URL.</param>
        /// <returns>ContentAccessor_MetaModel.</returns>
        /// <exception cref="System.Web.HttpException">404</exception>
        public static ContentAccessor_MetaModel GetRouteData(this string friendlyUrl)
        {
            string defaultLanguage = PortalEnvironment.DefaultLanguage;
            object eParameters = new { @friendlyUrl = friendlyUrl };
            string controller;
            string action;
            string language = defaultLanguage;
            int layoutMenuId;
            int structurePageId;
            string openingMessageResourceTag = string.Empty;
            string[] openingMessageResourceStringFormatParameters = new List<string>().ToArray();

            ContentAccessor_MetaModel toReturn = null;

            string loweredFriendlyUrl = friendlyUrl.ToLower();

            if (loweredFriendlyUrl == "/")
            {
                layoutMenuId = 1;
                controller = "DynaContentPublic";
                action = "Index";
                structurePageId = 1;
                toReturn = new ContentAccessor_MetaModel(friendlyUrl, controller, action, language, layoutMenuId, structurePageId, openingMessageResourceTag, openingMessageResourceStringFormatParameters);
            }
            else
            {
                //Recherche de l'adresse dans le proxy
                using (DataRepositories _dataContext = new DataRepositories())
                {
                    //Si l'adresse ne se termine pas par .htm, on ajoute index.htm à la fin
                    Structure_Page dbStructure_Page = null;
                    if (loweredFriendlyUrl.Length >= 5)
                    {
                        language = loweredFriendlyUrl.Substring(0, 5);
                    }

                    loweredFriendlyUrl = "/" + loweredFriendlyUrl;

                    string[] tLanguages = PortalEnvironment.Languages.Split(',');
                    string[] tHomes = tLanguages.Select(x => string.Format("/{0}", x)).ToArray();
                    //If language is not specified in url
                    if (!tLanguages.Contains(language))
                    {

                        loweredFriendlyUrl = "/";
                        openingMessageResourceTag = "FriendlyAnalyserError_LanguageNotSpecified";
                        openingMessageResourceStringFormatParameters = new string[] { HttpContext.Current.Request.Url.Authority + loweredFriendlyUrl };

                        string[] tUserLanguages = HttpContext.Current.Request.UserLanguages;
                        string[] tUserLanguagesAllowed = tLanguages.Intersect(tUserLanguages.Select(x => x.ToLower())).ToArray();

                        if (tUserLanguagesAllowed.Count() == 0)
                        {
                            language = defaultLanguage;
                        }
                        else
                        {
                            language = tUserLanguagesAllowed.First();
                        }
                    }
                    if (
                        loweredFriendlyUrl == string.Format("/{0}/index.htm", defaultLanguage)
                        || loweredFriendlyUrl == string.Format("/{0}/", defaultLanguage)
                        || loweredFriendlyUrl == string.Format("/{0}", defaultLanguage)
                        || loweredFriendlyUrl == "/"
                    )
                    {
                        loweredFriendlyUrl = "/";
                        dbStructure_Page = _dataContext.Structure_Page_Rep.Query(x => x.DirectURL == loweredFriendlyUrl && x.LayoutMenu_Translation.LayoutMenu.SortIndex == 1).FirstOrDefault();
                    }
                    else if (tHomes.Contains(loweredFriendlyUrl))
                    {
                        loweredFriendlyUrl = string.Format("/{0}", language);
                        dbStructure_Page = _dataContext.Structure_Page_Rep.Query(x => x.DirectURL == loweredFriendlyUrl && x.LayoutMenu_Translation.LayoutMenu.SortIndex == 1).FirstOrDefault();
                    }
                    else if (!loweredFriendlyUrl.EndsWith(".htm"))
                    {
                        if (!loweredFriendlyUrl.EndsWith("/"))
                        {
                            loweredFriendlyUrl += "/";
                        }
                        dbStructure_Page = _dataContext.Structure_Page_Rep.Query(x => x.DirectURL.ToLower().Contains(loweredFriendlyUrl) && x.LayoutMenu_Translation.LayoutMenu.SortIndex == 1).FirstOrDefault();
                    }
                    else
                    {
                        dbStructure_Page = _dataContext.Structure_Page_Rep.Query(x => x.DirectURL.ToLower() == loweredFriendlyUrl).FirstOrDefault();
                    }
                    if (dbStructure_Page == null)
                    {
                        toReturn = StructurePageNull(_dataContext, language, defaultLanguage, loweredFriendlyUrl);
                    }
                    else
                    {
                        if (dbStructure_Page.LayoutMenu_Translation == null)
                        {
                            Logger.Error(enLog.Business, new INNOVACALL.Framework.Common.InnovacallExceptions.HierarchyException(eMethodBase + "ContentAccessor_MetaModel", eParameters, Resources.HttpErrors404_ProxyHierarchyWasNull));
                            throw new HttpException(404, Resources.View_HttpError_404);
                        }
                        LayoutMenu_Translation dbLayoutMenu_Translation = dbStructure_Page.LayoutMenu_Translation;
                        LayoutMenu dbLayoutMenu = dbLayoutMenu_Translation.LayoutMenu;
                        layoutMenuId = dbLayoutMenu.Id;
                        controller = dbLayoutMenu.Controller;
                        if (controller.ToLower().EndsWith("controller"))
                        {
                            controller = controller.Substring(0, controller.Length - 10);
                        }
                        action = dbLayoutMenu.DefaultAction;
                        structurePageId = dbStructure_Page.Id;
                        toReturn = new ContentAccessor_MetaModel(loweredFriendlyUrl, controller, action, language, layoutMenuId, structurePageId, openingMessageResourceTag, openingMessageResourceStringFormatParameters);
                    }
                }
            }
            INNOVACALL.Framework.Common.MVCHelpers.Localization.CommonLocalization.SetCurrentThreadLanguage(language);
            return toReturn;
        }

        /// <summary>
        /// Structures the page null.
        /// </summary>
        /// <param name="_dataContext">The _data context.</param>
        /// <param name="language">The language.</param>
        /// <param name="defaultLanguage">The default language.</param>
        /// <param name="loweredFriendlyUrl">The lowered friendly URL.</param>
        /// <returns>ContentAccessor_MetaModel.</returns>
        /// <exception cref="System.Web.HttpException">404</exception>
        private static ContentAccessor_MetaModel StructurePageNull(DataRepositories _dataContext, string language, string defaultLanguage, string loweredFriendlyUrl)
        {
            object eParameters = new { _dataContext = _dataContext, language = language, defaultLanguage = defaultLanguage, loweredFriendlyUrl = loweredFriendlyUrl };
            ContentAccessor_MetaModel toReturn = null;
            int structurePageId = 1;
            string[] openingMessageResourceStringFormatParameters;
            Logger.Error(enLog.Business, new INNOVACALL.Framework.Common.InnovacallExceptions.HierarchyException(eMethodBase + "StructurePageNull", eParameters, Resources.HttpErrors404_ProxyWasNull));
            if (HttpContext.Current.Request.Browser.Crawler)
            {
                throw new HttpException(404, Resources.View_HttpError_404);
            }
            else
            {
                if (language != defaultLanguage)
                {
                    LayoutMenu_Translation layoutMenu_Translation = _dataContext.LayoutMenu_Translation_Rep.Query(x => x.FK_LayoutMenu == 1 && x.Language.Description == language).FirstOrDefault();
                    if (layoutMenu_Translation == null)
                    {
                        structurePageId = 1;
                    }
                    else
                    {
                        Structure_Page structurePage = layoutMenu_Translation.Structure_Page.OrderBy(x => x.SortIndex == 1).FirstOrDefault();
                        if (structurePage == null)
                        {
                            structurePageId = 1;
                        }
                        else
                        {
                            structurePageId = structurePage.Id;
                        }
                    }
                }
                openingMessageResourceStringFormatParameters = new string[] { HttpContext.Current.Request.Url.Authority + loweredFriendlyUrl };
                toReturn = new ContentAccessor_MetaModel("/", "DynaContentPublic", "Index", language, 1, structurePageId, "View_HttpError_404_Param", openingMessageResourceStringFormatParameters);
            }
            return toReturn;
        }
    }
}